package http;

import configuration.MyConfiguration;
import util.MyDateUtil;

import java.io.IOException;
import java.io.OutputStream;
import java.nio.charset.Charset;
import java.nio.charset.StandardCharsets;
import java.text.ParseException;
import java.util.*;

/**
 * @author Karl
 * @Date 2023/1/4 - 15:47
 */
public class MyHttpResponse {

    protected static Charset utf_8 = StandardCharsets.UTF_8;

    protected static String lineSeparator = System.lineSeparator();

    protected static byte[] lineByte = lineSeparator.getBytes(utf_8);

    protected String responseLine;
    protected Map<String, String> responseHeader = new HashMap<>();
    protected List<Byte> responseBody = new LinkedList<>();

    protected String host;
    protected int port = 80;
    protected String url;
    protected int status;
    protected boolean needCache = false;

    public void setResponseLine(String line) {
        this.responseLine = line;
        String[] temp = line.split("\\s+");
        status = Integer.parseInt(temp[1]);
    }

    public String getResponseLine() {
        return responseLine;
    }

    //会把整行的响应行包括\r\n加进来
    public void addResponseHeader(String headerName,String header) {
        responseHeader.put(headerName,header);
    }
    //会把整行的响应行包括\r\n加进来
    public void addResponseHeader(String header) {
        int idx = header.indexOf(':');
        if (idx != -1) {
            String headerName = header.substring(0, idx);
            if (headerName.equals("Host")) {
                String temp = header.substring(idx + 1);
                int idx2 = temp.indexOf(':');
                if (idx2 != -1) {
                    host = temp.substring(1, idx2);
                    port = Integer.parseInt(temp.substring(idx2 + 1));
                } else
                    host = temp.substring(1);
            } else if (headerName.equals("Proxy-Connection")) {
                headerName = "Connection";
                header = header.replace("Proxy-Connection", "Connection");
            }

            responseHeader.put(headerName, header);
        }
    }

    public Collection<String> getResponseHeader() {
        return responseHeader.values();
    }

    public void sendMessage(OutputStream lout) throws IOException {
        if (responseLine != null) {
            lout.write(responseLine.getBytes());
        }

        for (String header : responseHeader.values()) {
            lout.write(header.getBytes());
        }
        lout.write(lineByte);
        if (responseBody.size() != 0) {
            for (Byte aByte : responseBody) {
                lout.write(aByte);
            }
        }
        lout.flush();
    }


    public void addResponseBody(byte b) {
        this.responseBody.add(b);
//        responseBody[bodyLen++] = b;
    }

    public void addResponseBody(byte[] data, int len) {
        for (int i = 0; i < Math.min(data.length, len); i++) {
            responseBody.add(data[i]);
//            responseBody[bodyLen++] = data[i];
        }
    }

    public List<Byte> getResponseBody() {
        return responseBody;
    }

    public String getResponseHeader(String header) {
        return responseHeader.getOrDefault(header, null);
    }


    public int getStatus() {
        return status;
    }

    public int getContentLength() {
        if (responseHeader.containsKey("Content-Length")) {
            String header = responseHeader.get("Content-Length");
            int idx = header.indexOf(':');
            if (idx != -1) {
                //因为响应体格式是响应体名: (冒号+空格)响应头内容，所以+2
                return Integer.parseInt(header.substring(idx + 2).trim());
            }

        }
        return -1;
    }

    public boolean isChunked() {
        if (responseHeader.containsKey("Transfer-Encoding")) {
            String header = responseHeader.get("Transfer-Encoding");
            return header.contains("chunked");
        }
        return false;
    }

    public void setNeedCache(boolean needCache) {
        this.needCache = needCache;
    }

    public boolean isNeedCache() {
        return needCache;
    }







    /**
     * 查看请求头看是否缓存到期
     * @return 是否可用缓存,-1表示没有CacheExpireHeader，0表示已经过期
     */
    public long getCacheExpire() {
        if(responseHeader.containsKey(MyConfiguration.getCacheExpireHeader())){
            String expireTime = responseHeader.get(MyConfiguration.getCacheExpireHeader()).trim().split(": ")[1];
            try {
                long time;
                if((time = MyDateUtil.calGapMillTime(expireTime))<0)
                    return time;
                else return 0;
            } catch (ParseException e) {
                return -1;
            }
        }
        return -1;
    }

    public boolean containsHeader(String headerName) {
        return responseHeader.containsKey(headerName);
    }
}
